package deepbrain.simnetwork.task;

import deepbrain.simnetwork.network.Network;
import deepbrain.simnetwork.network.NetworkState;
import deepbrain.simnetwork.network.NodeState;

/**
 * 
 * 
 * @author Li Yang
 * @create 2009-2-24
 */
public abstract class SimulationTask extends Task {

	private static final long serialVersionUID = 67828387149195337L;

	protected Network network;
	protected NetworkState state;

	protected boolean running;

	protected boolean stochastic = false;

	public boolean isStochastic() {
		return stochastic;
	}

	public void setStochastic(boolean stochastic) {
		this.stochastic = stochastic;
	}

	public SimulationTask() {
	}

	public SimulationTask(Network network) {
		this.network = network;
	}

	public SimulationTask(Network network, NodeState[] state) {
		this(network, new NetworkState(state));
	}

	public SimulationTask(Network network, NetworkState state) {
		this.network = network;
		this.state = state;
	}

	public NetworkState getNetworkState() {
		return state;
	}

	public void setNetworkState(NetworkState state) {
		this.state = state;
	}

	public void setNetworkState(NodeState[] state) {
		this.state = new NetworkState(state);
	}

	public void setNetwork(Network network) {
		this.network = network;
	}

	public Network getNetwork() {
		return network;
	}

	public void runUntilCancelled() {
		running = true;
		while (true) {
			if (!running) {
				break;
			}
			runStep();
		}
		running = false;
	}

	public void runForSteps(int numOfSteps) {
		running = true;
		for (int i = 0; i < numOfSteps; i++) {
			if (!running) {
				return;
			}
			runStep();
		}
		running = false;
	}

	public void runStep() {
		processNetwork();
		fireStepFinish();
	}

	public void runOnce() {
		running = true;
		runStep();
		running = false;
	}

	public void processNetwork() {
		if (stochastic)
			this.state = network.nextNetworkState(state);
		else
			this.state = NetworkState.getRandomCertainNetwork(network
					.nextNetworkState(state));
	}

	public void stop() {
		running = false;
	}

}
